﻿using HomeCareLibrary.AppService.Mappers;
using HomeCareLibrary.Core.DataContracts;
using HomeCareLibrary.Core.Dtos;
using HomeCareLibrary.Core.JsonObjects;
using HomeCareLibrary.DataAccess;
using HomeCareLibrary.Repository;
using System.Collections.Generic;
using System.Linq;

namespace HomeCareLibrary.AppService
{
    public class PersonalisationAppService : AppServiceBase
    {
        /// <summary>
        /// Gets the features by user identifier home number.
        /// </summary>
        /// <param name="request">The request.</param>
        /// <returns></returns>
        public List<CTGetFeaturesByUserIdHomeNumberDto> GetFeaturesByUserIdHomeNumber(GetKLByUserIdHomeNumberRequest request)
        {
            var returnData = new List<CTGetFeaturesByUserIdHomeNumberDto>();
            if (request == null || (request.UserId == 0 || request.HomeNumber == 0))
            {
                return returnData;
            }

            using (var unitOfWork = new UnitOfWork())
            {
                var repository = new Repository<CTGetFeaturesByUserIdHomeNumber>(unitOfWork);
                var queryParameter = string.Format("@userId={0}, @homeNumber={1}", request.UserId, request.HomeNumber);

                var featuresData = repository.ExecuteFuntion("sp_App_PES_GetFeaturesByUserIdHomeNumber", queryParameter);
                return featuresData.ToDTOs();
            }
        }

        /// <summary>
        /// Gets the country states.
        /// </summary>
        /// <returns></returns>
        public List<CTGetCountryStatesDto> GetCountryStates()
        {
            var returnData = new List<CTGetCountryStatesDto>();

            using (var unitOfWork = new UnitOfWork())
            {
                var repository = new Repository<CTGetCountryStates>(unitOfWork);

                var countryStatesData = repository.ExecuteFuntion("sp_App_PES_GetCountryStates", string.Empty);
                return countryStatesData.ToDTOs();
            }
        }

        /// <summary>
        /// Gets the dwelling types.
        /// </summary>
        /// <returns></returns>
        public List<CTGetDwellingTypesDto> GetDwellingTypes()
        {
            var returnData = new List<CTGetDwellingTypesDto>();

            using (var unitOfWork = new UnitOfWork())
            {
                var repository = new Repository<CTGetDwellingTypes>(unitOfWork);

                var dwellingTypesData = repository.ExecuteFuntion("sp_App_PES_GetDwellingTypes", string.Empty);
                return dwellingTypesData.ToDTOs();
            }
        }

        /// <summary>
        /// Gets the features by dwelling code.
        /// </summary>
        /// <param name="request">The request.</param>
        /// <returns></returns>
        public List<CTGetFeaturesByDwellingCodeDto> GetFeaturesByDwellingCode(GetFeaturesByDwellingTypeRequest request)
        {
            var returnData = new List<CTGetFeaturesByDwellingCodeDto>();
            if (request == null || request.DwellingCode == 0)
            {
                return returnData;
            }
            using (var unitOfWork = new UnitOfWork())
            {
                var repository = new Repository<CTGetFeaturesByDwellingCode>(unitOfWork);
                var queryParameter = string.Format("@dwellingCode={0}", request.DwellingCode);

                var featuresData = repository.ExecuteFuntion("sp_App_PES_GetFeaturesByDwellingCode", queryParameter);
                return featuresData.ToDTOs();
            }
        }

        /// <summary>
        /// Gets the default features by dwelling code.
        /// </summary>
        /// <param name="request">The request.</param>
        /// <returns></returns>
        public List<Dwelling_FeaturesDto> GetDefaultFeaturesByDwellingCode(GetFeaturesByDwellingTypeRequest request)
        {
            using (var unitOfWork = new UnitOfWork())
            {
                var repository = new Repository<Dwelling_Features>(unitOfWork);
                return repository.Find(x => x.dwelling_code == request.DwellingCode && x.default_set == 1).ToDTOs();
            }
        }

        /// <summary>
        /// Gets the knowledge level by user identifier home number.
        /// </summary>
        /// <param name="request">The request.</param>
        /// <returns></returns>
        public List<CTGetKnowledgeLevelByUserIdHomeNumberDto> GetKnowledgeLevelByUserIdHomeNumber(GetKLByUserIdHomeNumberRequest request)
        {
            var returnData = new List<CTGetKnowledgeLevelByUserIdHomeNumberDto>();
            if (request == null || request.UserId == 0 || request.HomeNumber == 0)
            {
                return returnData;
            }

            using (var unitOfWork = new UnitOfWork())
            {
                var repository = new Repository<CTGetKnowledgeLevelByUserIdHomeNumber>(unitOfWork);
                var queryParameter = string.Format("@userId={0}, @homeNumber={1}", request.UserId, request.HomeNumber);

                var knowledgeLevelsData = repository.ExecuteFuntion("sp_App_PES_GetKnowledgeLevelByUserIdHomeNumber", queryParameter);
                if (knowledgeLevelsData != null)
                {
                    return knowledgeLevelsData.ToDTOs();
                }
                else
                {
                    return returnData;
                }
            }

        }

        /// <summary>
        /// Gets the location by user identifier home number.
        /// </summary>
        /// <param name="request">The request.</param>
        /// <returns></returns>
        public List<CTGetLocationByUserIdHomeNumberDto> GetLocationByUserIdHomeNumber(GetKLByUserIdHomeNumberRequest request)
        {
            var returnData = new List<CTGetLocationByUserIdHomeNumberDto>();
            if (request == null || request.UserId == 0 || request.HomeNumber == 0)
            {
                return returnData;
            }

            using (var unitOfWork = new UnitOfWork())
            {
                var repository = new Repository<CTGetLocationByUserIdHomeNumber>(unitOfWork);
                var queryParameter = string.Format("@userId={0}, @homeNumber={1}", request.UserId, request.HomeNumber);

                var locationsData = repository.ExecuteFuntion("sp_App_PES_GetLocationByUserIdHomeNumber", queryParameter);
                if (locationsData != null)
                    return locationsData.ToDTOs();
                else
                {
                    return returnData;
                }
            }
        }

        /// <summary>
        /// Gets the priority level by user identifier home number.
        /// </summary>
        /// <param name="request">The request.</param>
        /// <returns></returns>
        public List<CTGetPriorityLevelByUserIdHomeNumberDto> GetPriorityLevelByUserIdHomeNumber(GetKLByUserIdHomeNumberRequest request)
        {
            var returnData = new List<CTGetPriorityLevelByUserIdHomeNumberDto>();
            if (request == null || request.UserId == 0 || request.HomeNumber == 0)
            {
                return returnData;
            }

            using (var unitOfWork = new UnitOfWork())
            {
                var repository = new Repository<CTGetPriorityLevelByUserIdHomeNumber>(unitOfWork);
                var queryParameter = string.Format("@userId={0}, @homeNumber={1}", request.UserId, request.HomeNumber);

                var priorityLevelsData = repository.ExecuteFuntion("sp_App_PES_GetPriorityLevelByUserIdHomeNumber", queryParameter);
                if (priorityLevelsData != null)
                    return priorityLevelsData.ToDTOs();
                else
                {
                    return returnData;
                }
            }
        }

        /// <summary>
        /// Gets the monthly alert settings by user identifier home number.
        /// </summary>
        /// <param name="request">The request.</param>
        /// <returns></returns>
        public List<CTGetMonthlyAlertSettingsByUserIdHomeNumberDto> GetMonthlyAlertSettingsByUserIdHomeNumber(GetKLByUserIdHomeNumberRequest request)
        {
            var returnData = new List<CTGetMonthlyAlertSettingsByUserIdHomeNumberDto>();
            if (request == null || request.UserId == 0 || request.HomeNumber == 0)
            {
                return returnData;
            }

            using (var unitOfWork = new UnitOfWork())
            {
                var repository = new Repository<CTGetMonthlyAlertSettingsByUserIdHomeNumber>(unitOfWork);
                var queryParameter = string.Format("@userId={0}, @homeNumber={1}", request.UserId, request.HomeNumber);

                var alertSettingsData = repository.ExecuteFuntion("sp_App_PES_GetMonthlyAlertSettingsByUserIdHomeNumber", queryParameter);
                return alertSettingsData.ToDTOs();
            }
        }

        /// <summary>
        /// Gets the goals by user identifier home number.
        /// </summary>
        /// <param name="request">The request.</param>
        /// <returns></returns>
        public List<CTGetGoalsByUserIdHomeNumberDto> GetGoalsByUserIdHomeNumber(GetKLByUserIdHomeNumberRequest request)
        {
            var returnData = new List<CTGetGoalsByUserIdHomeNumberDto>();
            if (request == null || request.UserId == 0 || request.HomeNumber == 0)
            {
                return returnData;
            }

            using (var unitOfWork = new UnitOfWork())
            {
                var repository = new Repository<CTGetGoalsByUserIdHomeNumber>(unitOfWork);
                var queryParameter = string.Format("@userId={0}, @homeNumber={1}", request.UserId, request.HomeNumber);

                var goalsData = repository.ExecuteFuntion("sp_App_PES_GetGoalsByUserIdHomeNumber", queryParameter);
                if (goalsData != null)
                {
                    return goalsData.ToDTOs();
                }
                else
                {
                    return returnData;
                }
            }
        }

        /// <summary>
        /// Gets the user homes.
        /// </summary>
        /// <param name="request">The request.</param>
        /// <returns></returns>
        public List<CTGetUserHomesDto> GetUserHomes(GetUserHomeRequest request)
        {
            var returnData = new List<CTGetUserHomesDto>();
            if (request == null || request.UserId == 0)
            {
                return returnData;
            }
            using (var unitOfWork = new UnitOfWork())
            {
                var repository = new Repository<CTGetUserHomes>(unitOfWork);
                var queryParameter = string.Format("@userId={0}", request.UserId);

                var homesData = repository.ExecuteFuntion("sp_App_PES_GetUserHomes", queryParameter);
                return homesData.ToDTOs();
            }

        }

        /// <summary>
        /// Updates the personalization.
        /// </summary>
        /// <param name="personlisationData">The personlisation data.</param>
        /// <returns></returns>
        public string UpdatePersonalization(PersonalizationData personlisationData)
        {
            using (var unitOfWork = new UnitOfWork())
            {
                var repository = new Repository<User_Details>(unitOfWork);
                //var queryParameter = string.Format("@userID={0}, @homeNumber={1}, @homeName='{2}', @dwellingType='{3}', @featurestring='{4}', @psPriority='{5}', @psKnowledgeLevel='{6}', @psCountry='{7}', @psStateProvince='{8}', @psGoalString='{9}', @welcomeImage='{10}', @webMoAlert='{11}'",
                //    personlisationData.UserId, personlisationData.HomeNumber, personlisationData.HomeName,
                //    personlisationData.DwellingType, personlisationData.FeatureString.Replace("'", "''").Replace("\"", @""""), personlisationData.Priority,
                //    personlisationData.KnowledgeLevel, personlisationData.Country, personlisationData.StateProvince,
                //    personlisationData.Goal, personlisationData.WelcomeImage, personlisationData.WebMOAlertEmail);
                var queryParameter = string.Format("@userID={0}, @homeNumber={1}, @homeName='{2}', @dwellingType='{3}', @featurestring='{4}', @psKL='{5}', @psCountry='{6}', @psGoalString='{7}', @webMoAlertEmail='{8}', @appMoAlertWeek={9}, @appMoAlertDay={10}, @appMoAlertHour={11},@appMoAlertBadge={12},@appMoAlertpopUp={13},@psPriority={14},@psStateProvince='{15}'",
                   personlisationData.UserId, personlisationData.HomeNumber, personlisationData.HomeName,
                   personlisationData.DwellingType, personlisationData.FeatureString.Replace("'", "''").Replace("\"", @""""), personlisationData.KnowledgeLevel,
                   personlisationData.Country, string.IsNullOrEmpty(personlisationData.Goal) ? string.Empty : personlisationData.Goal.Replace("'", "''"), 
                   personlisationData.WebMOAlertEmail,personlisationData.AppMoAlertWeek,personlisationData.AppMoAlertDay,
                   personlisationData.AppMoAlertHour,personlisationData.AppMoAlertBadge,personlisationData.AppMoAlertPopup,
                   personlisationData.Priority, personlisationData.StateProvince);
                var result = repository.ExecuteSQLCommand("sp_App_PES_UpdatePersonalization", queryParameter);

                if (result > 0)
                    return "Success";
                else
                    return "No update done";
            }

        }

        /// <summary>
        /// Add home details
        /// </summary>
        /// <param name="userId">The user identifier.</param>
        /// <returns></returns>
        public User_DetailsDto AddHome(int userId)
        {
            using (var unitOfWork = new UnitOfWork())
            {
                var repository = new Repository<User_Details>(unitOfWork);
                var queryParameter = string.Format("@userID={0}",userId.ToString());
                var result = repository.ExecuteFuntion("sp_App_PES_AddHome", queryParameter).ToDTOs().FirstOrDefault();
                return result;
            }
        }


        /// <summary>
        /// Delete home details
        /// </summary>
        /// <param name="homeData">The home data.</param>
        /// <returns></returns>
        public string DeleteHome(HomeData homeData)
        {

            using (var unitOfWork = new UnitOfWork())
            {
                var repository = new Repository<User_Details>(unitOfWork);

                var queryParameter = string.Format("@userID={0}, @homeNumber={1}",
                  homeData.UserId, homeData.HomeNumber);
                var result = repository.ExecuteSQLCommand("sp_App_PES_DeleteHome", queryParameter);
                if (result > 0)
                    return "Success";
                else
                    return "No records to delete.";

            }
        
        }
       

        /// <summary>
        /// Gets the dwelling types.
        /// </summary>
        /// <returns></returns>
        public List<Dwelling_TypesDto> ListDwellingTypes()
        {
            using (var unitOfWork = new UnitOfWork())
            {
                var repository = new Repository<Dwelling_Types>(unitOfWork);
                return repository.GetAll().ToDTOs();
            }
        }

        /// <summary>
        /// Fetches the feature categories.
        /// </summary>
        /// <returns></returns>
        public List<HomeCareLibraryCategoryDto> FetchFeatureCategories()
        {
            using (var unitOfWork = new UnitOfWork())
            {
                var repository = new Repository<HomeCareLibraryCategory>(unitOfWork);
                return repository.Find(x => x.ID != 7).ToDTOs();
            }
        }

        /// <summary>
        /// Gets the feature by identifier.
        /// </summary>
        /// <param name="featureId">The feature identifier.</param>
        /// <returns></returns>
        public FeatureDto GetFeatureById(string featureId)
        {
            using (var unitOfWork = new UnitOfWork())
            {
                var repository = new Repository<HomeCareLibrary.DataAccess.Feature>(unitOfWork);
                return repository.FirstOrDefault(x => x.feature_code == featureId).ToDTO();
            }
        }

        public Dictionary<string, object> GetFeaturesByUserIdHomeNumberDwellingType(int userId, int homeNumber, int dwellingType)
        {
            bool hasDwellingTypeChanged = true;
            Dictionary<string, object> featuresData = new Dictionary<string, object>();
            List<FeatureCategory> featureCategories = new List<FeatureCategory>();
            FeatureCategory featureCategory = null;
            HomeCareLibrary.Core.JsonObjects.Feature feature = null;
            int categoryId = 0;

            using (var unitOfWork = new UnitOfWork())
            {
                var repository = new Repository<User_Details>(unitOfWork);
                var user = repository.FirstOrDefault(x => x.user_id == userId && x.home_number == homeNumber).ToDTO();
                if (user != null)
                {
                    if (user.dwelling_type == dwellingType)
                    {
                        hasDwellingTypeChanged = false;
                    }
                }
                featuresData.Add("hasDwellingTypeChanged", hasDwellingTypeChanged);
            }

            using (var unitOfWork = new UnitOfWork())
            {
                var repository = new Repository<CTGetFeaturesByUserIdHomeNumberDwellingType>(unitOfWork);
                var queryParameter = string.Format("@paramUserId={0}, @paramHomeNumber={1}, @paramDwellingType={2}",userId, homeNumber,dwellingType);
                var features = repository.ExecuteFuntion("sp_get_Features_By_UserId_HomeNumber_And_DwellingType", queryParameter).ToDTOs();
                //features = features.Take(20).ToList();
                if (features != null && features.Count > 0)
                {
                    features.ForEach(fet =>
                    {
                        if (categoryId != fet.category_id)
                        {
                            featureCategory = new FeatureCategory();
                            featureCategory.id = fet.category_id;
                            featureCategory.category = fet.category;
                            featureCategories.Add(featureCategory);
                            categoryId = fet.category_id;
                        }
                        feature = new HomeCareLibrary.Core.JsonObjects.Feature();
                        feature.featureCode = fet.feature_code;
                        feature.featureName = fet.feature_name;
                        feature.isSelected = fet.isSelected == 1? true : false;
                        featureCategory.features.Add(feature);
                    });
                }
                featuresData.Add("featureCategories", featureCategories);
            }
            return featuresData;
        }

        public Dictionary<string,string> GetLocationGoalsKnowPriorityByUserIdHomeNumber(GetKLByUserIdHomeNumberRequest request)
        {
            var location = GetLocationByUserIdHomeNumber(request).FirstOrDefault();
            var priority = GetPriorityLevelByUserIdHomeNumber(request).FirstOrDefault();
            var knowledgeLevel = GetKnowledgeLevelByUserIdHomeNumber(request).FirstOrDefault();
            var goal = GetGoalsByUserIdHomeNumber(request).FirstOrDefault();

            var dictionaryData = new Dictionary<string, string>();
            dictionaryData.Add("userId", request.UserId.ToString());
            dictionaryData.Add("homeNumber", request.HomeNumber.ToString());
            dictionaryData.Add("psCountry", location.ps_country);
            dictionaryData.Add("psStateProvince", location.ps_state_province);
            dictionaryData.Add("psPriority", priority.ps_priority.HasValue ? priority.ps_priority.Value.ToString() : string.Empty);
            dictionaryData.Add("psGoalString", goal.ps_goal_string);
            dictionaryData.Add("psKnowledgeLevel", knowledgeLevel.ps_knowledge_level.HasValue ? knowledgeLevel.ps_knowledge_level.Value.ToString() : string.Empty);

            return dictionaryData;
        }

        /// <summary>
        /// Gets the monthly special feature articles.
        /// </summary>
        /// <param name="date">date</param>
        /// <returns></returns>
        //public List<CTGetMonthlySpecialFeaturesArticlesDto> GetMonthlySpecialFeaturesArticles(string date)
        //{
        //    var returnData = new List<CTGetMonthlySpecialFeaturesArticlesDto>();
        //    if (date == null)
        //    {
        //        return returnData;
        //    }

        //    using (var unitOfWork = new UnitOfWork())
        //    {
        //        var repository = new Repository<CTGetMoSpecialFeaturesArticles>(unitOfWork);
        //        var queryParameter = date;

        //        var featuresData = repository.ExecuteFuntion("sp_get_Monthly_Special_Features_Articles", queryParameter);
        //        return featuresData.ToDTOs();
        //    }
        //}
    }
}
